import * as vscode from 'vscode';
import * as fs from 'fs';
import * as path from 'path';
import { getCurrentUserId } from './userUtil';
import { AuthService } from './authService';




export class MyFlatListViewProvider implements vscode.WebviewViewProvider {
  public static readonly viewType = 'myFlatListView';
  public _view?: vscode.WebviewView;
  public static _currentInstance: MyFlatListViewProvider | undefined;
  private static _taskSource: (() => { id: number; title: string; assigneeId?: any; statusId?: any; statusName?: string; description?: string; desc?: string; status?: string; typeName?: string; type?: string }[]) | undefined;
  private authService: AuthService;

  constructor(private readonly context: vscode.ExtensionContext) {
    MyFlatListViewProvider._currentInstance = this;
    this.authService = new AuthService(context);
  }

  static setTaskSource(fn: () => { id: number; title: string; assigneeId?: any; statusId?: any; statusName?: string; description?: string; desc?: string; status?: string; typeName?: string; type?: string }[]) {
    MyFlatListViewProvider._taskSource = fn;
  }

  static refreshAll() {
    MyFlatListViewProvider._currentInstance?.refresh();
  }

  static clearTasks() {
    if (MyFlatListViewProvider._currentInstance && MyFlatListViewProvider._currentInstance._view) {
      // 清空 webview 内容
      MyFlatListViewProvider._currentInstance._view.webview.html = MyFlatListViewProvider._currentInstance.getHtml([]);
    }
  }

  refresh() {
    if (this._view) {
      // 调试日志
      // eslint-disable-next-line no-console
      console.log('[MyFlatListViewProvider.refresh] this._view:', this._view);
      // 保证每次刷新都重新排序
      const items = MyFlatListViewProvider._taskSource?.() || [];
      // 调试日志
      // eslint-disable-next-line no-console
      console.log('[MyFlatListViewProvider.refresh] items:', items);
      // eslint-disable-next-line no-console
      console.log('[MyFlatListViewProvider.refresh] items.length:', items.length);
      if (items.length === 0) {

        return;
      }
      const sortedItems = items.slice().sort((a, b) => {
        if (a.status === b.status) return 0;
        if (a.status === '进行中') return -1;
        return 1;
      });
      this._view.webview.html = this.getHtml(sortedItems);
    }
  }

  resolveWebviewView(
    webviewView: vscode.WebviewView,
    context: vscode.WebviewViewResolveContext,
    _token: vscode.CancellationToken
  ) {
    this._view = webviewView;
    webviewView.webview.options = {
      enableScripts: true
    };

    // 任务数据由外部注入
    const items = MyFlatListViewProvider._taskSource?.() || [];
    // 进行中排前面，未开始排后面
    const sortedItems = items.slice().sort((a, b) => {
      if (a.status === b.status) return 0;
      if (a.status === '进行中') return -1;
      return 1;
    });

    webviewView.webview.html = this.getHtml(sortedItems);

    webviewView.webview.onDidReceiveMessage(async msg => {

      console.log('[Webview] 收到消息:', msg);
      if (msg.command === 'markDone') {
        vscode.window.showInformationMessage(`任务ID ${msg.id} 已完成！`);
        vscode.commands.executeCommand('myFlatListView.markDone', msg.id);

      }

      // 移除 saveApiKey 相关逻辑
      // if (msg.command === 'saveApiKey') { ... }
      

      // 在 getSavedConfig 里移除 setApiKey 消息发送
      if (msg.command === 'getSavedConfig') {
        const isLoggedIn = await require('./authService').isLoggedIn(this.context);
        console.log('[Webview] isLoggedIn:', isLoggedIn);
        if (!isLoggedIn) {
          vscode.window.showWarningMessage('请先登录后再操作');
          console.log('getSavedConfig弹窗已调用');
          return;
        }
        // const apiKey = this.context.globalState.get('codingApiKey', '');
        const projectName = this.context.globalState.get('codingProjectName', '');
        // webviewView.webview.postMessage({ command: 'setApiKey', apiKey }); // 删除
        webviewView.webview.postMessage({ command: 'setProjectName', projectName });
        // 自动拉取项目列表
        const apiKey = this.context.globalState.get('codingApiKey', '');
        if (apiKey) {
          const userId = await getCurrentUserId(this.context, this.authService);
          const projects = await fetchCodingProjects(apiKey, userId);
          webviewView.webview.postMessage({ command: 'setProjects', projects, projectName });
        }
        // 新增：每次初始化都清空任务列表和分项目缓存并刷新视图为空
        await this.context.globalState.update('taskList', []);
        if (projectName) {
          await this.context.globalState.update(`taskList_${projectName}`, []);
        }
        MyFlatListViewProvider.refreshAll();
      }
      if (msg.command === 'fetchProjects') {
        const isLoggedIn = await require('./authService').isLoggedIn(this.context);
        console.log('[Webview] isLoggedIn:', isLoggedIn);
        if (!isLoggedIn) {
          if (this._view) {
            this._view.webview.postMessage({ command: 'showInfo', text: '请先登录后再操作' });
          }
          return;
        }
        const apiKey = msg.apiKey || this.context.globalState.get('codingApiKey', '');
        if (!apiKey) {
          webviewView.webview.postMessage({ command: 'showInfo', text: '请先输入API Key' });
          return;
        }
        const userId = await getCurrentUserId(this.context, this.authService);
        const projects = await fetchCodingProjects(apiKey, userId);
        webviewView.webview.postMessage({ command: 'setProjects', projects });
      }
      if (msg.command === 'saveProjectName') {
        const projectName = msg.projectName || '';
        await this.context.globalState.update('codingProjectName', projectName);
        // 切换项目时清空所有任务缓存和UI
        const allKeys = this.context.globalState.keys();
        for (const key of allKeys) {
          if (key.startsWith('taskList_') || key === 'taskList') {
            await this.context.globalState.update(key, []);
          }
        }
        // 新增：清空webview内容
        this._view && (this._view.webview.html = this.getHtml([]));
        MyFlatListViewProvider.refreshAll();
        // vscode.window.showInformationMessage('已切换项目，请点击刷新按钮加载任务');
      }
      if (msg.command === 'saveProjectNameAndRefresh') {
        const projectName = msg.projectName || '';
        await this.context.globalState.update('codingProjectName', projectName);
        // 切换项目时清空所有任务缓存和UI
        const allKeys = this.context.globalState.keys();
        for (const key of allKeys) {
          if (key.startsWith('taskList_') || key === 'taskList') {
            await this.context.globalState.update(key, []);
          }
        }
        MyFlatListViewProvider.refreshAll();
        // 拉取当前项目任务
        vscode.commands.executeCommand('taskList.manualRefresh');
      }
      if (msg.command === 'refreshTasks') {
        const isLoggedIn = await require('./authService').isLoggedIn(this.context);
        if (!isLoggedIn) {
          if (this._view) {
            this._view.webview.postMessage({ command: 'showInfo', text: '请先登录后再操作' });
          }
          return;
        }
        const projectName = this.context.globalState.get('codingProjectName', '');
        const apiKey = this.context.globalState.get('codingApiKey', '');
        if (!projectName) {
          vscode.window.showWarningMessage('请先选择项目后再刷新任务列表');
          return;
        }
        if (!apiKey) {
          vscode.window.showWarningMessage('请先设置 API Key 后再刷新任务列表');
          return;
        }
        // 只清空当前项目缓存和UI
        await this.context.globalState.update('taskList', []);
        if (projectName) {
          await this.context.globalState.update(`taskList_${projectName}`, []);
        }
        MyFlatListViewProvider.refreshAll();
        // 拉取当前项目任务
        setTimeout(() => {
          vscode.commands.executeCommand('taskList.manualRefresh');
        }, 100);
      }
      if (msg.command === 'closeTask') {
        vscode.commands.executeCommand('myFlatListView.closeTask', msg.id);
      }
      // 收到 setTasks 时清空任务列表
      if (msg.command === 'setTasks') {
        const listEl = document.querySelector('.list');
        if (listEl) listEl.innerHTML = '<div style="color:#888;text-align:center;margin:24px 0;">暂无任务</div>';
      }

    });
  }

  getHtml(items: { id: number; title: string; assigneeId?: any; statusId?: any; statusName?: string; description?: string; desc?: string; status?: string; typeName?: string; type?: string }[]): string {
    // 类型映射
    const typeMap: Record<string, string> = {
      'REQUIREMENT': '需求',
      'DEFECT': '缺陷',
      'SUB_TASK': '工作项'
    };
    const typeOrder: Array<keyof typeof typeMap> = ['REQUIREMENT', 'DEFECT', 'SUB_TASK'];
    // 状态映射表
    const statusMap: Record<string, Record<string, '未完成' | '进行中' | '已完成'>> = {
      REQUIREMENT: {
        '未开始': '未完成',
        '需求确认': '进行中',
        '测试中': '进行中',
        '进行中': '进行中',
        '待验证': '进行中',
        '已完成': '已完成',
        '已关闭': '已完成',
        '已结束': '已完成',
      },
      DEFECT: {
        '未开始': '未完成',
        '测试中': '进行中',
        '待验证': '进行中',
        '进行中': '进行中',
        '已完成': '已完成',
        '拒绝': '已完成',
        '已结束': '已完成',
      },
      SUB_TASK: {
        '未开始': '未完成',
        '需求确认': '进行中',
        '测试中': '进行中',
        '进行中': '进行中',
        '待验证': '进行中',
        '已完成': '已完成',
        '已关闭': '已完成',
        '已结束': '已完成',
      }
    };
    // 组内排序优先级
    const statusOrder = { '进行中': 0, '未完成': 1, '已完成': 2 };
    // 预处理分组，映射状态并排序，只保留进行中和未完成
    const grouped: { [key: string]: any[] } = {};
    items.forEach(item => {
      const type = item.type as keyof typeof typeMap;
      const rawStatus = item.statusName || item.status || '';
      const mappedStatus = statusMap[type]?.[rawStatus] || '未完成';
      // debug: 打印 SUB_TASK 的状态映射
      if (type === 'SUB_TASK') {
        // eslint-disable-next-line no-console
        console.log('[getHtml][SUB_TASK]', {
          id: item.id,
          title: item.title,
          rawStatus,
          mappedStatus,
          statusId: item.statusId,
          statusName: item.statusName,
        });
      }
      if (mappedStatus === '已完成') return; // 过滤已完成
      if (!grouped[type]) grouped[type] = [];
      grouped[type].push({ ...item, mappedStatus });
    });
    // 每组内排序
    Object.keys(grouped).forEach(type => {
      grouped[type].sort((a, b) => {
        return statusOrder[(a.mappedStatus as keyof typeof statusOrder)] - statusOrder[(b.mappedStatus as keyof typeof statusOrder)];
      });
    });
    // 只渲染有数据的分组，顺序固定
    const itemsHtml = typeOrder.filter(type => grouped[type] && grouped[type].length > 0).map((type, idx) =>
      `${idx > 0 ? '<hr class="group-separator" />' : ''}` +
      `<div class="group-title" id="group-title-${type}" onclick="toggleGroup('${type}')">
        <svg class="group-arrow" viewBox="0 0 20 20"><path d="M7 8l3 3 3-3" stroke="#3578d4" stroke-width="2" fill="none" stroke-linecap="round"/></svg>
        <span>${typeMap[type]}</span>
      </div>
      <div class="group-content" id="group-content-${type}">
        ${grouped[type].map((item) => {
        const desc = item.description || item.desc || '';
        return `
            <div class="item">
              ${this.getStatusIcon(item.mappedStatus)}
              <span class="title" title="${desc ? desc.replace(/\"/g, '&quot;') : ''}">${item.title}</span>
              ${item.mappedStatus === '进行中' ? `
                <button class="action-btn" title="标记为已完成" data-task-id="${item.id}">
                  <svg class="action-icon" viewBox="0 0 20 20" style="fill: var(--vscode-gitDecoration-addedResourceForeground, #43c463);"><path d="M7.629 15.314a1 1 0 0 1-1.414 0l-3.536-3.536a1 1 0 1 1 1.414-1.414l2.829 2.828 6.364-6.364a1 1 0 1 1 1.414 1.414l-7.071 7.072z"/></svg>
                </button>
                <button class="action-btn" title="关闭任务" data-task-id="${item.id}">
                  <svg class="action-icon" viewBox="0 0 20 20" style="stroke: var(--vscode-gitDecoration-deletedResourceForeground, #f66); fill: none;"><path d="M6 6l8 8M14 6l-8 8" stroke-width="2" stroke-linecap="round"/></svg>
                </button>
              ` : ''}
            </div>
          `;
      }).join('')}
      </div>
    `).join('');
    // 读取模板文件
    const templatePath = path.join(this.context.extensionPath, 'src', 'myFlatListView.html');
    let template = '';
    try {
      template = fs.readFileSync(templatePath, 'utf-8');
    } catch (e) {
      return `<div style="color:red">HTML模板文件未找到: ${templatePath}</div>`;
    }
    return template.replace('{{items}}', itemsHtml);
  }

  getStatusIcon(mappedStatus: string): string {
    if (mappedStatus === '进行中') {
      // 蓝色实心圆
      return `<svg class="status-icon" viewBox="0 0 20 20"><circle cx="10" cy="10" r="6" fill="#3578d4"/></svg>`;
    }
    if (mappedStatus === '已完成') {
      // 绿色实心圆
      return `<svg class="status-icon" viewBox="0 0 20 20"><circle cx="10" cy="10" r="6" fill="#43c463"/></svg>`;
    }
    // 未完成 - 灰色空心圆
    return `<svg class="status-icon" viewBox="0 0 20 20"><circle cx="10" cy="10" r="6" fill="none" stroke="#aaa" stroke-width="2"/></svg>`;
  }
}

// 拉取CODING项目列表
export async function fetchCodingProjects(apiKey: string, userId: number): Promise<Array<{ Name: string, DisplayName: string }>> {
  const axios = require('axios');
  try {
    const resp = await axios.post(
      'https://e.coding.net/open-api/?Action=DescribeUserProjects&action=DescribeUserProjects',
      { UserId: userId },
      {
        headers: {
          'Accept': 'application/json',
          'Authorization': `token ${apiKey}`,
          'Content-Type': 'application/json'
        },
        timeout: 8000
      }
    );
    // 新增：打印原始响应
    console.log('[fetchCodingProjects] resp.data:', resp.data);
    if (resp.data && resp.data.Response && resp.data.Response.Error) {
      const code = resp.data.Response.Error.Code;
      if (code === 'UnauthorizedOperation') {
        vscode.window.showErrorMessage('API 权限不够，无法获取项目列表（UnauthorizedOperation）');
        return [];
      }
    }
    return (resp.data.Response.ProjectList || []).map((p: any) => ({ Name: p.Name, DisplayName: p.DisplayName }));
  } catch (e) {
    return [];
  }
}